package com.earthea.application.task.quartz;

import com.earthea.application.task.TaskService;
import com.earthea.application.task.entity.TaskConstants;
import com.earthea.application.utils.BaseLogUtils;
import com.earthea.common.constant.LogConstants;
import com.google.common.collect.Maps;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.ThreadUtils;
import org.quartz.JobDataMap;
import org.quartz.JobDetail;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.quartz.QuartzJobBean;

import java.time.Duration;
import java.util.Map;
import java.util.Optional;

public class TaskArchivingQuartzJob extends QuartzJobBean {

    private static final String JOB_NAME = "TaskArchivingQuartzJob";

    @Autowired
    private TaskService taskService;

    @Override
    protected void executeInternal(JobExecutionContext context) throws JobExecutionException {
        JobDataMap jobDataMap =
                Optional.of(context).map(JobExecutionContext::getJobDetail).map(JobDetail::getJobDataMap).orElse(new JobDataMap());

        int limit = Integer.parseInt(StringUtils.defaultIfBlank(jobDataMap.getString("limit"),
                String.valueOf(TaskConstants.DEFAULT_ARCHIVING_LIMIT)));

        Map<String, String> logParams = Maps.newLinkedHashMap();
        logParams.put("limit", String.valueOf(limit));
        BaseLogUtils.printJobLog(JOB_NAME, LogConstants.BEGIN, logParams);

        try {
            int total = 0;
            int count = taskService.archiving(limit);
            total += count;
            while (count > 0) {
                ThreadUtils.sleepQuietly(Duration.ofMillis(100));
                count = taskService.archiving(limit);
                total += count;
            }
            logParams.put("total", String.valueOf(total));
            BaseLogUtils.printJobLog(JOB_NAME, LogConstants.END, logParams);
        } catch (Exception e) {
            logParams.put("error", e.getMessage());
            BaseLogUtils.printJobLog(JOB_NAME, LogConstants.FAIL, logParams);
        }
    }
}
